package ai.parser;

import java.io.BufferedReader;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
import java.text.NumberFormat;
import java.text.ParseException;
import java.util.ArrayList;
import java.util.List;


public class ImageParser {
	
	/** Le nom du fichier image à charger */
	private String fileName;
	
	/** Le buffer de lecture du fichier */
	private BufferedReader br;
	
	public ImageParser(String fileName) {
		this.fileName = fileName;
	}
	
	/**
	 * Ouvre le fichier d'image
	 */
	public void open() {
		try {
			FileReader fr = new FileReader(fileName);
		    this.br = new BufferedReader(fr);
		} catch (FileNotFoundException e) {
			e.printStackTrace();
		}	
	}
	
	/**
	 * Fermer le fichier
	 */
	public void close() {
		try {
			this.br.close();
		} catch (IOException e) {
			e.printStackTrace();
		}
	}
	
	/** Charge une image à partir d'une string
	 * @input string correspondant à une image
	 * @return Une liste correspondant aux valeurs de chaque pixel
	 * @throws ParseException 
	 */
	public double[] parseImage(String line) throws ParseException {
		
		/** séparer toutes les valeurs en utilisant l'espace comme délimitateur */
		String[] splited = line.split("\\s+");
		
		/** convertir le tableau en arraylist de double*/
		double[] result = new double[784];
		NumberFormat nf = NumberFormat.getInstance();
		int j = 0;
		for (int i = 0; i < splited.length; i++) {
			if (!splited[i].equals("")) {
				result[j] = nf.parse(splited[i]).doubleValue();
				j++;
			}
		}
		return result;
	}
	
        /**
         * Fait la moyenne des points sur un carré
         * @param entry Entrée à l'origine
         * @param sizeFilter Longueur du carré
         * @return 
         */
        public double[] filterEntry(double[] entry, final int sizeFilter) {
            double[] ret = new double[sizeFilter];
            int size = (int)Math.sqrt(entry.length);
            double treat;
            for(int i = 0; i < size; i+=sizeFilter) {
                treat = 0.0;
                for (int j = 0; j < sizeFilter; j++){
                    for (int k = 0; k < sizeFilter; k++){
                        treat += entry[j*size + k];
                    }
                }
                ret[i/sizeFilter] = (treat/(size*size));
            }
            return ret;
        }
        
	/** Charge une image contenue dans le fichier,
	 * nécéssite que le fichier ai été ouvert avant.  
	 * @return Une liste de double correspondant à une image
	 */
	public double[] loadImage() {
		final int sizeFilter = 2;
		double[] result = new double[784];
                
		try {
			result = filterEntry(parseImage(br.readLine()), sizeFilter);
		} catch (ParseException e) {
			e.printStackTrace();
		} catch (IOException e) {
			e.printStackTrace();
		}
		
		return result;
	}
	
	public String getFileName() {
		return fileName;
	}

	public void setFileName(String fileName) {
		this.fileName = fileName;
	}

}
